package com.ctg.behavior.calc.impala.transfer.usergroups;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import com.alibaba.fastjson.JSON;
import com.ctg.behavior.calc.common.CtSQLParam;
import com.ctg.behavior.calc.impala.report.CtCalcRestrictMeasureReport;
import com.ctg.behavior.calc.impala.transfer.CtFilterTransfer;
import com.ctg.behavior.calc.impala.transfer.CtHavingRestrictTransfer;
import com.ctg.behavior.calc.impala.transfer.CtLimitRestrictTransfer;
import com.ctg.behavior.calc.impala.transfer.CtTimeRestrictTransfer;
import com.ctg.behavior.calc.utils.CtCalcPropertyUtils;
import com.ctg.behavior.calc.utils.CtCalcSQLUtils;
import com.ctg.behavior.common.calc.CtCalc;
import com.ctg.behavior.common.consts.CtCalcConsts;

import lombok.extern.slf4j.Slf4j;

@Slf4j
@Component
public class CtUGUBMeasureTransfer extends CtFilterTransfer {

	@Autowired
	private CtTimeRestrictTransfer timeRestrictTransfer;
	@Autowired
	private CtHavingRestrictTransfer havingRestrictTransfer;
	@Autowired
	private CtLimitRestrictTransfer limitRestrictTransfer;

	/******************************************************
	 * @apiNote:
	 */
	@Override
	public String doTransfer(CtCalc calcObject, CtSQLParam sqlParam) {
		if (!(calcObject instanceof CtCalcRestrictMeasureReport)) {
			log.warn("calcObject is not CtCalcRestrictMeasureReport, class={}", calcObject.getClass());
			log.warn("calcObject: {}", JSON.toJSON(calcObject));
			return "";
		}
		CtCalcRestrictMeasureReport measure = (CtCalcRestrictMeasureReport) calcObject;
		log.info("CalcBody={}", JSON.toJSONString(measure));
		
		String property = CtCalcPropertyUtils.getProperty(measure.getField());

		StringBuilder impalaSQL = new StringBuilder();

		// 1. SELECT 部分：
		{
			impalaSQL.append(" SELECT user_id AS user_id ");
		}
		// 2. 表关联
		{
			if (CtCalcConsts.GROUPBY_DAY.equalsIgnoreCase(property)) {
				// 2.1 分布 - 天数 ===> 需要按device_id,event_date分组，增加一个字段查询
				impalaSQL.append(" FROM ( ");
				impalaSQL.append(" SELECT user_id,event,event_date ");
				impalaSQL.append(" FROM a_event_parquet_").append(measure.getAppId());
				impalaSQL.append(" WHERE event = '").append(measure.getEventId()).append("' ");
				// 时间限制也要加上，防数据量过大
				{
					String sqlCondtions = timeRestrictTransfer.doTransfer(measure.getTimeRestrict(), sqlParam);
					if (!CtCalcSQLUtils.isEmptyCondtions(sqlCondtions)) {
						impalaSQL.append(" AND ").append(sqlCondtions);
					}
				}
				impalaSQL.append(" GROUP BY user_id,event,event_date ");
				impalaSQL.append(" ) T0 ");
			} else {
				// 2.2 根据APP_ID来决定查询哪个表
				impalaSQL.append(" FROM a_event_parquet_").append(measure.getAppId());
			}
			impalaSQL.append(" WHERE 1=1 ");
		}
		// 3. 事件标识条件
		{
			impalaSQL.append(" AND event = '").append(measure.getEventId()).append("' ");
		}
		// 4. 筛选条件 - Filter
		{
			String sqlCondtions = super.doTransfer(measure.getFilter(), sqlParam);
			if (!CtCalcSQLUtils.isEmptyCondtions(sqlCondtions)) {
				impalaSQL.append(" AND ").append(sqlCondtions);
			}
		}
		// 5. 时间限制 - timeRestrict
		{
			String sqlCondtions = timeRestrictTransfer.doTransfer(measure.getTimeRestrict(), sqlParam);
			if (!CtCalcSQLUtils.isEmptyCondtions(sqlCondtions)) {
				impalaSQL.append(" AND ").append(sqlCondtions);
			}
		}
		// 6. group by
		{
			impalaSQL.append(" GROUP BY user_id ");
		}
		// 7. 计算度量限制 - restrict ===> 通过having方式实现
		{
			String havingCondtions = havingRestrictTransfer.doTransfer(measure, sqlParam);
			if (!CtCalcSQLUtils.isEmptyCondtions(havingCondtions)) {
				impalaSQL.append(havingCondtions);
			}
		}
		// 8. 处理LIMIT & ORDER BY
		{
			String limitCondtions = limitRestrictTransfer.doTransfer(measure, sqlParam);
			if (!CtCalcSQLUtils.isEmptyCondtions(limitCondtions)) {
				impalaSQL.append(limitCondtions);
			}
		}
		
		String retSQL = impalaSQL.toString();
		log.info("CalcSQL={}", impalaSQL);

		return retSQL;
	}

}
